package com.laxcen.smoke.test;

import com.laxcen.smoke.util.SortUtils;
import net.sf.json.JSONObject;
import org.apache.commons.httpclient.*;
import org.apache.commons.httpclient.methods.GetMethod;
import org.apache.commons.httpclient.params.HttpMethodParams;
import org.springframework.stereotype.Service;

import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.UnsupportedEncodingException;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
import java.text.SimpleDateFormat;
import java.util.*;

@Service
public class LV {
    private static String HTTPMethod = "GET";

    //云端API参数
//    private String Action = "QueryDeviceRecordLifeCycle";
//    private String Parameters  = "";
//    @Value("${accessKey}")
//    private String accesskey;

    public static void main(String[] args) throws UnsupportedEncodingException {
        get();
    }

        public static JSONObject get() throws UnsupportedEncodingException {
            Map<String, String> map = new HashMap<String, String>();
            map.put("Format","JSON");
            map.put("Version","2018-01-20");
            map.put("AccessKeyId","LTAI5tQqhoe1XSrkoCWkDDQ9");
            map.put("SignatureMethod","HMAC-SHA1");
            SimpleDateFormat dateFormatGmt = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSSXXX");
            dateFormatGmt.setTimeZone(TimeZone.getTimeZone("GMT"));
            map.put("Timestamp",dateFormatGmt.format(new Date()));
            map.put("SignatureVersion","1.0");
            map.put("SignatureNonce",UUID.randomUUID().toString());
            map.put("RegionId","cn-shanghai");
            map.put("Action","QueryDeviceRecordLifeCycle");
            //排序
            String sort = SortUtils.formatUrlParam(map,"utf-8",false);
            System.out.println(sort);
            //HTTPMethod：发送请求的HTTP方法，例如GET。
            //percentEncode("/")：字符（/）UTF-8编码得到的值，即%2F。
            String StringToSign= HTTPMethod + "&"+percentEncode("/") + "&" + percentEncode(sort); //您的规范化请求字符串。
            System.out.println(StringToSign);
            byte[] bytes = hamcsha1(StringToSign,"MXycRe3SmNlDPKuLNt1cfxhFyjk5Cf&");
            String sign = getBase64String(bytes);
            System.out.println(sign);
            map.put("Signature",sign);
            String Parameters = "&Format="+map.get("Format")+"&Version="+map.get("Version")+"&AccessKeyId="+map.get("AccessKeyId")+"&Signature="+map.get("Signature")+"&SignatureMethod="+map.get("SignatureMethod")+"&Timestamp="+map.get("Timestamp")+"&SignatureVersion="+map.get("SignatureVersion")+"&SignatureNonce="+map.get("SignatureNonce")+"&RegionId="+map.get("RegionId");
            String url = "http://linkvisual.cn-shanghai.aliyuncs.com/?Action="+"QueryDeviceRecordLifeCycle"+Parameters;
            System.out.println(url);
            String result = doGet(url,"utf-8");
            JSONObject jsonObject = new JSONObject();
            jsonObject.fromObject(result);
            return  jsonObject;
        }

    public static String getBase64String(byte[] s) {
        return Base64.getEncoder().encodeToString(s);
    }

    public static byte[] hamcsha1(String data, String key) {
        try {
            SecretKeySpec signingKey = new SecretKeySpec(key.getBytes(), "HmacSHA1");
            Mac mac = Mac.getInstance("HmacSHA1");
            mac.init(signingKey);
            return mac.doFinal(data.getBytes());
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }


    private static final String ENCODING = "UTF-8";
    private static String percentEncode(String value) throws UnsupportedEncodingException {
        return value != null ? URLEncoder.encode(value, ENCODING).replace("+", "%20").replace("*", "%2A").replace("%7E", "~") : null;
    }


    /**
     * httpClient的get请求方式
     * 使用GetMethod来访问一个URL对应的网页实现步骤：
     * 1.生成一个HttpClient对象并设置相应的参数；
     * 2.生成一个GetMethod对象并设置响应的参数；
     * 3.用HttpClient生成的对象来执行GetMethod生成的Get方法；
     * 4.处理响应状态码；
     * 5.若响应正常，处理HTTP响应内容；
     * 6.释放连接。
     * @param url
     * @param charset
     * @return
     */
    public static String doGet(String url, String charset){
        /**
         * 1.生成HttpClient对象并设置参数
         */
        HttpClient httpClient = new HttpClient();
        //设置Http连接超时为5秒
        httpClient.getHttpConnectionManager().getParams().setConnectionTimeout(5000);

        /**
         * 2.生成GetMethod对象并设置参数
         */
        GetMethod getMethod = new GetMethod(url);
        //设置get请求超时为5秒
        getMethod.getParams().setParameter(HttpMethodParams.SO_TIMEOUT, 5000);
        //设置请求重试处理，用的是默认的重试处理：请求三次
        getMethod.getParams().setParameter(HttpMethodParams.RETRY_HANDLER, new DefaultHttpMethodRetryHandler());

        String response = "";

        /**
         * 3.执行HTTP GET 请求
         */
        try {
            int statusCode = httpClient.executeMethod(getMethod);

            /**
             * 4.判断访问的状态码
             */
            if (statusCode != HttpStatus.SC_OK){
                System.err.println("请求出错：" + getMethod.getStatusLine());
            }

            /**
             * 5.处理HTTP响应内容
             */
            //HTTP响应头部信息，这里简单打印
            Header[] headers = getMethod.getResponseHeaders();
            for (Header h: headers){
                System.out.println(h.getName() + "---------------" + h.getValue());
            }
            //读取HTTP响应内容，这里简单打印网页内容
            //读取为字节数组
            byte[] responseBody = getMethod.getResponseBody();
            response = new String(responseBody, charset);
            System.out.println("-----------response:" + response);
            //读取为InputStream，在网页内容数据量大时候推荐使用
            //InputStream response = getMethod.getResponseBodyAsStream();

        } catch (HttpException e) {
            //发生致命的异常，可能是协议不对或者返回的内容有问题
            System.out.println("请检查输入的URL!");
            e.printStackTrace();
        } catch (IOException e){
            //发生网络异常
            System.out.println("发生网络异常!");
        }finally {
            /**
             * 6.释放连接
             */
            getMethod.releaseConnection();
        }
        return response;
    }


    private static String httpURLGETCase(String methodUrl) {
        HttpURLConnection connection = null;
        BufferedReader reader = null;
        String line = null;
        try {
            URL url = new URL(methodUrl); // 参数
            // 根据URL生成HttpURLConnection
            connection = (HttpURLConnection) url.openConnection();
            // 默认GET请求
            connection.setRequestMethod("GET");
            // 建立TCP连接
            connection.connect();
            if (connection.getResponseCode() == HttpURLConnection.HTTP_OK) {
                // 发送http请求
                reader = new BufferedReader(new InputStreamReader(connection.getInputStream(), "UTF-8"));
                StringBuilder result = new StringBuilder();
                // 循环读取流
                while ((line = reader.readLine()) != null) {
                    result.append(line).append(System.getProperty("line.separator"));
                }
                String s = result.toString();
                System.out.println(s); // 获取的数据
                return s;
            }
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                reader.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
            connection.disconnect();
        }
        return null;
    }
}
